package com.netty.cn.model.http;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.netty.cn.model.http.handler.JsoncatHandler;

import io.netty.bootstrap.ServerBootstrap;
import io.netty.channel.Channel;
import io.netty.channel.ChannelInitializer;
import io.netty.channel.ChannelOption;
import io.netty.channel.EventLoopGroup;
import io.netty.channel.epoll.Epoll;
import io.netty.channel.epoll.EpollEventLoopGroup;
import io.netty.channel.epoll.EpollServerSocketChannel;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.SocketChannel;
import io.netty.channel.socket.nio.NioServerSocketChannel;
import io.netty.handler.codec.http.HttpObjectAggregator;
import io.netty.handler.codec.http.HttpRequestDecoder;
import io.netty.handler.codec.http.HttpResponseEncoder;
import io.netty.handler.logging.LogLevel;
import io.netty.handler.logging.LoggingHandler;


/**
 * 
 * @author wangzonghui
 * @date 2021-11-02 14:56:41
 * @Description 服务定义
 */
public class JsoncatServer {
	
	private final Logger log = LoggerFactory.getLogger(this.getClass());
	
	public static void main(String[] args) {
		new JsoncatServer().start();
	}
	
	private final int PORT = 8080;

    public void start() {
        EventLoopGroup bossGroup = Epoll.isAvailable() ? new EpollEventLoopGroup() : new NioEventLoopGroup();
        EventLoopGroup workerGroup = Epoll.isAvailable() ? new EpollEventLoopGroup() : new NioEventLoopGroup();
        
        try {
            ServerBootstrap b = new ServerBootstrap();
            b.group(bossGroup, workerGroup)
                    .channel(Epoll.isAvailable() ? EpollServerSocketChannel.class : NioServerSocketChannel.class)
                    // TCP默认开启了 Nagle 算法，该算法会尽可能发送大数据快，减少网络传输。 参数：TCP_NODELAY，控制是否启用 Nagle 算法。
                    .childOption(ChannelOption.TCP_NODELAY, true)
                    // 开启 TCP 底层心跳机制
                    .childOption(ChannelOption.SO_KEEPALIVE, true)
                    //表示系统临时存放已完成三次握手的请求的队列的最大长度,如果连接数过多造成建立频繁，导致服务器创建新连接较慢，可适当调大这个参数
                    .option(ChannelOption.SO_BACKLOG, 128)
                    .handler(new LoggingHandler(LogLevel.INFO))
                    .childHandler(new ChannelInitializer<SocketChannel>() {
                        @Override
                        protected void initChannel(SocketChannel ch) {
                            ch.pipeline().addLast("decoder", new HttpRequestDecoder())
                                    .addLast("encoder", new HttpResponseEncoder())
                                    .addLast("aggregator", new HttpObjectAggregator(1*1024 * 1024))
                                    .addLast("handler", new JsoncatHandler());
                        }
                    });
            Channel ch = b.bind(PORT).sync().channel();
            log.info("Http服务启动，端口：{}，访问地址：http://localhost:{}", PORT,PORT);
            ch.closeFuture().sync();
            
        } catch (InterruptedException e) {
            log.error("occur com.github.jsoncat.exception when start com.github.jsoncat.server:", e);
        } finally {
            log.error("shutdown bossGroup and workerGroup");
            bossGroup.shutdownGracefully();
            workerGroup.shutdownGracefully();
        }
    }

}
